package bje;

import static org.junit.Assert.assertTrue;
import robocode.control.events.BattleCompletedEvent;
import robocode.control.events.TurnEndedEvent;
import robocode.control.snapshot.IBulletSnapshot;
import robocode.control.testing.RobotTestBed;

/**
 * This tests for variability in bullet power administered by the robot Surfer. Looks only at
 * Surfer's bullets. TODO: Add other interesting behavioral tests.
 * 
 * @author Jeffrey Beck
 */
public class TestSurferFiring extends RobotTestBed {

  // True if Surfer has fired a bullet with power less than 1.4;
  boolean firePowerReachLevelOne = false;
  // True if Surfer has fired a bullet with power between 1.5 to 1.9;
  boolean firePowerReachLevelTwo = false;
  // True if Surfer has fired a bullet with power between 2.0 to 2.4;
  boolean firePowerReachLevelThree = false;
  // True if Surfer has fired a bullet with power greater than 2.4;
  boolean firePowerReachLevelFour = false;

  /**
   * Specifies that sample.Tracker and Surfer are to be matched up in this test case.
   * 
   * @return The comma-delimited list of robots in this match.
   */
  @Override
  public String getRobotNames() {

    return "sample.Tracker, bje.Surfer";
  }

  /**
   * Runs this test for 10 rounds.
   * 
   * @return The number of rounds.
   */
  @Override
  public int getNumRounds() {

    return 10;
  }

  /**
   * At the end of each turn, checks the power of all bullets moving across the battlefield. Checks
   * to see if there is any variability in bullet power, proving that Surfer is using proportional
   * firing based on distance of detected enemy robot and battlefield width.
   * 
   * @param event Info about the current state of the battle.
   */
  @Override
  public void onTurnEnded(TurnEndedEvent event) {

    IBulletSnapshot bullets[] = event.getTurnSnapshot().getBullets();

    double bulletPower;
    int bulletOwner;

    for (int i = 0; i < bullets.length; i++) {

      // only look at Surfer's bullets, should be element 1 in the array
      bulletOwner = bullets[i].getOwnerIndex();

      if (bulletOwner == 1) {

        bulletPower = bullets[i].getPower();

        if (bulletPower <= 1.4) {
          firePowerReachLevelOne = true;
        }
        else if (bulletPower > 1.5 && bulletPower <= 1.9) {
          firePowerReachLevelTwo = true;
        }
        else if (bulletPower > 1.9 && bulletPower <= 2.4) {
          firePowerReachLevelThree = true;
        }
        else if (bulletPower > 2.4) {
          firePowerReachLevelFour = true;
        }
      }
    }

  }

  /**
   * After running all matches, determine if Surfer has had variability in its bullet power.
   * 
   * @param event Details about the completed battle.
   */
  @Override
  public void onBattleCompleted(BattleCompletedEvent event) {

    assertTrue("Bullet Power less than 1.4", firePowerReachLevelOne);
    assertTrue("Bullet Power between 1.5 and 1.9", firePowerReachLevelTwo);
    assertTrue("Bullet Power between 2.0 and 2.4", firePowerReachLevelThree);
    assertTrue("Bullet Power greater than 2.5", firePowerReachLevelFour);
  }
}